<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>D3-Celestial Supernova Remnants</title>
  <script type="text/javascript" src="../lib/d3.min.js"></script>
  <script type="text/javascript" src="../lib/d3.geo.projection.min.js"></script>
  <script type="text/javascript" src="../celestial.min.js"></script>
  <link rel="stylesheet" href="../celestial.css">
</head>
<body>
  <div style="overflow:hidden;margin:0 auto;"><div id="celestial-map"></div></div>
  <div id="celestial-form"></div>

  <script type="text/javascript">

// Some prettifying styles
var config = {
  projection: "aitoff",
  transform: "galactic",
  background: { fill: "#fff", stroke: "#000", opacity: 1, width: 1 },
  datapath: "https://ofrohn.github.io/data/",
  stars: {
    colors: false,
    names: false,
    style: { fill: "#000", opacity:1 },
    limit: 6,
    size: 5
  },
  dsos: { show: false, size: 10 },
  mw: {
    style: { fill:"#996", opacity: 0.1 }
  },
};

// Asterisms canvas style properties for lines and text
var pointStyle = {
      stroke: "rgba(255, 0, 204, 1)",
      fill: "rgba(255, 0, 204, 0.15)"
    },
    textStyle = {
      fill:"rgba(255, 0, 204, 1)",
      font: "normal bold 15px Helvetica, Arial, sans-serif",
      align: "left",
      baseline: "bottom"
    };

// JSON structure of the object to be displayed, in this case
// the Summer Triangle between Vega, Deneb and Altair
var jsonSnr = {
  "type":"FeatureCollection",
  // this is an array, add as many objects as you want
  "features":[
    {"type":"Feature",
     "id":"SomeDesignator",
     "properties": {
       // Name
       "name":"Some Name",
       // Size in arcminutes
       "dim": 10
     }, "geometry":{
       // the line object as an array of point coordinates
       "type":"Point",
       "coordinates": [-80.7653, 38.7837]
     }
    }
  ]};

// Closest distance between labels
var PROXIMITY_LIMIT = 20;

Celestial.add({
  type:"json",
  file:"https://ofrohn.github.io/data/dsos.20.json",

  callback: function(error, json) {

    if (error) return console.warn(error);
    // Load the geoJSON file and transform to correct coordinate system, if necessary
    var dsos = Celestial.getData(json, config.transform);

    // Add to celestiasl objects container in d3
    Celestial.container.selectAll(".snrs")
      .data(dsos.features.filter(function(d) {
        return d.properties.type === 'snr'
      }))
      .enter().append("path")
      .attr("class", "snr");
    // Trigger redraw to display changes
    Celestial.redraw();
  },

  redraw: function() {

    var m = Celestial.metrics(), // Get the current map size in pixels
        // empty quadtree, will be used for proximity check
        quadtree = d3.geom.quadtree().extent([[-1, -1], [m.width + 1, m. height + 1]])([]);

    // Select the added objects by class name as given previously
    Celestial.container.selectAll(".snr").each(function(d) {
      // If point is visible (this doesn't work automatically for points)
      if (Celestial.clip(d.geometry.coordinates)) {
        // get point coordinates
        var pt = Celestial.mapProjection(d.geometry.coordinates);
        // object radius in pixel, could be varable depending on e.g. magnitude
        var r = Math.pow(parseInt(d.properties.dim) * 0.25, 0.5);

        // draw on canvas
        // Set object styles
        Celestial.setStyle(pointStyle);
        // Start the drawing path
        Celestial.context.beginPath();
        // Thats a circle in html5 canvas
        Celestial.context.arc(pt[0], pt[1], r, 0, 2 * Math.PI);
        // Finish the drawing path
        Celestial.context.closePath();
        // Draw a line along the path with the prevoiusly set stroke color and line width
        Celestial.context.stroke();
        // Fill the object path with the prevoiusly set fill color
        Celestial.context.fill();

        // Find nearest neighbor
        var nearest = quadtree.find(pt);

        // If neigbor exists, check distance limit
        if (!nearest || distance(nearest, pt) > PROXIMITY_LIMIT) {
          // Nothing too close, add it and go on
          quadtree.add(pt)
          // Set text styles
          Celestial.setTextStyle(textStyle);
          // and draw text on canvas with offset
          Celestial.context.fillText(d.properties.name, pt[0] + r + 2, pt[1] + r + 2);
        }
      }
    });
  }
});

// Simple point distance function
function distance(p1, p2) {
  var d1 = p2[0] - p1[0],
      d2 = p2[1] - p1[1];
  return Math.sqrt(d1 * d1 + d2 * d2);
}

Celestial.display(config);

  </script>

  <footer id="d3-celestial-footer">
    <p><a href="https://github.com/ofrohn/d3-celestial"><b>D3-Celestial</b></a> released under <a href="http://opensource.org/licenses/BSD-3-Clause">BSD license</a>. Copyright 2015-19 <a href="http://armchairastronautics.blogspot.com/" rel="author">Olaf Frohn</a>.</p>
  </footer>
</body>
</html>
